package net.cl.util.ui;
/**
 * @author David Bauske (1242618)
 */

import java.awt.Color;
import java.awt.Font;
import java.awt.Graphics;

import javax.swing.JTextField;
import javax.swing.event.DocumentEvent;
import javax.swing.event.DocumentListener;

/**
 * Simple class extending JTextField that provides the possibility to display a placeholder String when the field is
 * empty.
 *
 * Implementation detail: The placeholder is not really the text in the text field, it is just rendered there. Thus it
 * can neither be removed nor selected. That is the default behaviour of a placeholder text field, just as you expect it
 * to work when you use HTML's placeholder-attribute.
 *
 * @author David Bauske
 */
public class PlaceholderTextField extends JTextField
{
	private static final long	serialVersionUID	= -7700381711198386172L;

	private static final double	INTENSITY_DECREASE	= 0.6;
	private static final int	LIGHT_THRESHOLD		= 128;

	private String				mPlaceholder		= "";
	private Color				mPlaceholderColor;
	private boolean				mPlaceholderActive	= true;

	public PlaceholderTextField()
	{

	}

	/**
	 * Constructs a new PlaceholderTextField.
	 *
	 * @param pPlaceholder The placeholder text.
	 */
	public PlaceholderTextField(String pPlaceholder)
	{
		mPlaceholder = pPlaceholder;

		this.getDocument().addDocumentListener(new DocumentListener()
		{
			@Override
			public void changedUpdate(DocumentEvent event)
			{
				PlaceholderTextField.this.onTextChanged();
			}

			@Override
			public void insertUpdate(DocumentEvent arg0)
			{
				PlaceholderTextField.this.onTextChanged();
			}

			@Override
			public void removeUpdate(DocumentEvent arg0)
			{
				PlaceholderTextField.this.onTextChanged();
			}
		});

		mPlaceholderColor = computeWeakenedColor(Color.BLACK);
		mPlaceholderActive = true;
	}

	@Override
	public void setForeground(Color pColor)
	{
		super.setForeground(pColor);
		mPlaceholderColor = computeWeakenedColor(pColor);
	}

	/**
	 * Checks whether there's text from the user in the TextArea.
	 *
	 * @return true if the user entered text, false if the field (a) is empty or (b) contains the placeholder
	 */
	public boolean isEmpty()
	{
		return super.getText().length() == 0;
	}

	private void onTextChanged()
	{
		mPlaceholderActive = super.getText().length() == 0;
	}

	@Override
	protected void paintComponent(Graphics g)
	{
		super.paintComponent(g);

		if(this.mPlaceholderActive)
		{
			Font font = this.getFont();
			g.setFont(font);
			int yPos = (int) (getHeight() / 2.0 + (1.0 / 3.0) * g.getFontMetrics().getHeight());

			g.setColor(mPlaceholderColor);
			g.drawString(mPlaceholder, 6, yPos);
		}
	}

	private static Color computeWeakenedColor(Color pOrigin)
	{
		boolean lightColor = false;

		int red = pOrigin.getRed();
		int green = pOrigin.getGreen();
		int blue = pOrigin.getBlue();

		if(red > LIGHT_THRESHOLD)
		{
			lightColor = true;
		}
		else if(green > LIGHT_THRESHOLD)
		{
			lightColor = true;
		}
		else if(blue > LIGHT_THRESHOLD)
		{
			lightColor = true;
		}

		if(lightColor)
		{
			return new Color((int) (red * INTENSITY_DECREASE), (int) (green * INTENSITY_DECREASE),
					(int) (blue * INTENSITY_DECREASE), pOrigin.getAlpha());
		}
		else
		{
			return new Color((red + LIGHT_THRESHOLD), (green + LIGHT_THRESHOLD),
					(blue + LIGHT_THRESHOLD), pOrigin.getAlpha());
		}
	}
}